aboutsummaryrefslogtreecommitdiffstats
path: root/src/app/groups/[groupId]/expenses/create-from-receipt-button-actions.ts
diff options
context:
space:
mode:
authorSebastien Castiel <sebastien@castiel.me>2024-01-30 16:36:29 -0500
committerGitHub <noreply@github.com>2024-01-30 16:36:29 -0500
commit4a9bf575bd24b2e24348c65d9fbbf9c81a73cb35 (patch)
tree364cb36ea89d8023676140ed2fdd166c3b1fd602 /src/app/groups/[groupId]/expenses/create-from-receipt-button-actions.ts
parent9e300e0ff0c9d93cbaeaa86c1e2a560523107382 (diff)
Create expense from receipt (#69)
* Create expense from receipt * Add modal * Update README
Diffstat (limited to 'src/app/groups/[groupId]/expenses/create-from-receipt-button-actions.ts')
-rw-r--r--src/app/groups/[groupId]/expenses/create-from-receipt-button-actions.ts48
1 files changed, 48 insertions, 0 deletions
diff --git a/src/app/groups/[groupId]/expenses/create-from-receipt-button-actions.ts b/src/app/groups/[groupId]/expenses/create-from-receipt-button-actions.ts
new file mode 100644
index 0000000..1714f82
--- /dev/null
+++ b/src/app/groups/[groupId]/expenses/create-from-receipt-button-actions.ts
@@ -0,0 +1,48 @@
+'use server'
+import { getCategories } from '@/lib/api'
+import { env } from '@/lib/env'
+import OpenAI from 'openai'
+
+const openai = new OpenAI({ apiKey: env.OPENAI_API_KEY })
+
+export async function extractExpenseInformationFromImage(imageUrl: string) {
+ 'use server'
+ const categories = await getCategories()
+
+ const body = {
+ model: 'gpt-4-vision-preview',
+ messages: [
+ {
+ role: 'user',
+ content: [
+ {
+ type: 'text',
+ text: `
+ This image contains a receipt.
+ Read the total amount and store it as a non-formatted number without any other text or currency.
+ Then guess the category for this receipt amoung the following categories and store its ID: ${categories.map(
+ ({ id, grouping, name }) => `"${grouping}/${name}" (ID: ${id})`,
+ )}.
+ Guess the expense’s date and store it as yyyy-mm-dd.
+ Guess a title for the expense.
+ Return the amount, the category, the date and the title with just a comma between them, without anything else.`,
+ },
+ ],
+ },
+ {
+ role: 'user',
+ content: [{ type: 'image_url', image_url: { url: imageUrl } }],
+ },
+ ],
+ }
+ const completion = await openai.chat.completions.create(body as any)
+
+ const [amountString, categoryId, date, title] = completion.choices
+ .at(0)
+ ?.message.content?.split(',') ?? [null, null, null, null]
+ return { amount: Number(amountString), categoryId, date, title }
+}
+
+export type ReceiptExtractedInfo = Awaited<
+ ReturnType<typeof extractExpenseInformationFromImage>
+>